package com.luoguijia.disk.files.control;

import com.alibaba.fastjson.JSON;
import com.luoguijia.disk.files.entity.SearchFileEntity;
import com.luoguijia.disk.files.exception.FileOperationException;
import com.luoguijia.disk.files.service.FileIoService;
import com.luoguijia.disk.files.service.FileIoServiceImpl;
import com.luoguijia.disk.files.service.FileService;
import com.luoguijia.disk.mybatis.entity.PtFileEntity;
import com.luoguijia.disk.mybatis.flexigrid.PagingEntity;
import com.luoguijia.disk.mybatis.flexigrid.TblResponseEntity;
import com.luoguijia.disk.spring.control.BaseController;
import com.obs.services.ObsClient;
import com.obs.services.model.ObsObject;
import org.apache.ibatis.annotations.Param;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.i18n.LocaleContextHolder;
import org.springframework.core.io.InputStreamResource;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;

import javax.annotation.Resource;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Controller
@RequestMapping("/file")
public class FileController extends BaseController {

    @GetMapping("/getFileList")
    public List<PtFileEntity> getFileList() {
        return fileService.getFileList();
    }


    @Autowired
    @Resource
    private FileService fileService;

    @PostMapping("/upload")
    public String uploadFile(@RequestParam("file") MultipartFile file) {
        return fileService.uploadFile(file);
    }


    @Resource
    private FileIoService fileIoService;

    @RequestMapping("/fileAll")
    public String fileAll() {
        return "file/filePage";
    }


    @RequestMapping("/syncFileData")
    @ResponseBody
    public String syncFileData() {
        fileIoService.syncFileData();
        return successJson("file.sync.data.success");

    }

    @RequestMapping("/queryFileInfoListByPage")
    @ResponseBody
    public String queryFileInfoListByPage(SearchFileEntity entity, PagingEntity paging) {

        TblResponseEntity<PtFileEntity> tblResponseEntity = fileService.queryFileInfoListByPage(entity, paging);
        return JSON.toJSONString(tblResponseEntity);
    }

   /* @RequestMapping("/queryFileInfoById")
    @ResponseBody
    public String queryFileInfoById(@Param("fileUuid") String fileUuid) {

        PtFileEntity ptFileEntity = fileService.queryFileInfoById(fileUuid);
        return JSON.toJSONString(ptFileEntity);
    }
*/
    @RequestMapping("/deleteFileByIds")
    @ResponseBody
    public String deleteFileByIds(@RequestParam("ids") String ids) {
        fileService.deleteFileByIds(ids);
        return successJson("delete.file.success");
    }


    // 注意：若前端是表单提交，也可用 @PostMapping，根据实际需求调整
    @DeleteMapping("/file/delete/{fileId}")
    @ResponseBody
    public String deleteFile(@PathVariable String fileId) {
        boolean success = fileService.logicDeleteFile(fileId);
        return success ? "删除成功，文件已移入回收站" : "删除失败（文件不存在或无权限）";
    }

    // 文件页面
    @RequestMapping("/getFileInfolistBy")
    @ResponseBody
    public String getFileInfolistBy() {
        return "getFileInfolistBy/getFileInfolistByPage";
    }

    /**
     * 生成文件分享链接
     *
     * @param fileId 文件ID
     * @return 分享链接
     */
    @GetMapping("/generateShareLink")
    @ResponseBody
    public String generateShareLink(@RequestParam("fileId") String fileId) {
        try {
            String shareLink = fileService.generateShareLink(fileId);
            Map<String, String> result = new HashMap<>();
            result.put("shareLink", shareLink);
            return JSON.toJSONString(result);
        } catch (Exception e) {
            return failJson("generate.share.link.error", e.getMessage());
        }
    }

//文件下载
    @RequestMapping("/downFile/{fileUuid}")
    @ResponseBody
    public ResponseEntity<byte[]> downFile(@PathVariable("fileUuid") String fileUuid){
        ResponseEntity<byte[]> responseEntity = fileIoService.downFile(fileUuid);
        return responseEntity;
    }
    /**
     * 媒体文件在线预览接口
     */
    @GetMapping("/preview/{fileId}")
    public ResponseEntity<InputStreamResource> previewFile(@PathVariable String fileId) throws IOException, FileOperationException {
        // 1. 获取文件信息
        PtFileEntity file = fileService.getFileById(fileId);
        if (file == null) {
            return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
        }

        // 2. 将Integer类型的fileType转换为String后验证文件类型
        Integer fileTypeInt = file.getFileType();
        String contentType = getContentType(fileTypeInt);
        if (contentType == null) {
            return ResponseEntity.status(HttpStatus.UNSUPPORTED_MEDIA_TYPE)
                    .body(null);
        }

        // 注意：这里需要补充从ObsClient获取文件流的逻辑
        // 示例代码框架：
        // ObsObject obsObject = fileIoService.getObsClient().getObject(bucketName, objectKey);
        // InputStreamResource resource = new InputStreamResource(obsObject.getObjectContent());

        // 暂时返回Not Implemented状态，需要你根据实际文件存储方式实现
        return ResponseEntity.status(HttpStatus.NOT_IMPLEMENTED).body(null);
    }

    /**
     * 扩展支持的媒体类型映射，接收Integer类型的fileType并转换为String处理
     *
     * @param fileType 整数类型的文件类型标识
     */
    private String getContentType(Integer fileType) {
        // 如果fileType为null，直接返回不支持
        if (fileType == null) {
            return null;
        }

        // 将Integer转换为String
        String fileTypeStr = fileType.toString();

        // 视频类型映射
        Map<String, String> videoTypes = new HashMap<>();
        videoTypes.put("1", "video/mp4");    // 假设1代表mp4
        videoTypes.put("2", "video/x-msvideo"); // 假设2代表avi
        videoTypes.put("3", "video/quicktime"); // 假设3代表mov
        videoTypes.put("4", "video/x-ms-wmv");  // 假设4代表wmv
        videoTypes.put("5", "video/x-flv");     // 假设5代表flv
        videoTypes.put("6", "video/x-matroska");// 假设6代表mkv

        // 音频类型映射
        Map<String, String> audioTypes = new HashMap<>();
        audioTypes.put("10", "audio/mpeg");    // 假设10代表mp3
        audioTypes.put("11", "audio/wav");     // 假设11代表wav
        audioTypes.put("12", "audio/ogg");     // 假设12代表ogg
        audioTypes.put("13", "audio/flac");    // 假设13代表flac
        audioTypes.put("14", "audio/aac");     // 假设14代表aac

        // 检查整数类型对应的文件类型
        if (videoTypes.containsKey(fileTypeStr)) {
            return videoTypes.get(fileTypeStr);
        } else if (audioTypes.containsKey(fileTypeStr)) {
            return audioTypes.get(fileTypeStr);
        }

        // 如果找不到匹配的类型，返回null表示不支持
        return null;
    }
    // 回收站相关接口

    /**
     * 获取回收站文件列表
     */
    @RequestMapping("/recycle/list")
    @ResponseBody
    public String getRecycleFileList(SearchFileEntity entity, PagingEntity paging) {
        TblResponseEntity<PtFileEntity> tblResponseEntity = fileService.queryRecycleFileListByPage(entity, paging);
        return JSON.toJSONString(tblResponseEntity);
    }

    /**
     * 恢复单个文件
     */
    @PostMapping("/recycle/restore")
    @ResponseBody
    public String restoreFile(@RequestParam("fileId") String fileId) {
        try {
            boolean success = fileService.restoreFileFromRecycle(fileId);
            return success ? successJson("recyclebin.restore.success") : failJson("recyclebin.restore.fail");
        } catch (Exception e) {
            return failJson("recyclebin.restore.error", e.getMessage());
        }
    }

    /**
     * 永久删除单个文件
     */
    @PostMapping("/recycle/delete")
    @ResponseBody
    public String permanentlyDeleteFile(@RequestParam("fileId") String fileId) {
        try {
            boolean success = fileService.permanentlyDeleteFile(fileId);
            return success ? successJson("recyclebin.permanent.delete.success") : failJson("recyclebin.permanent.delete.fail");
        } catch (Exception e) {
            return failJson("recyclebin.permanent.delete.error", e.getMessage());
        }
    }

    /**
     * 批量恢复文件
     */
    @PostMapping("/recycle/batchRestore")
    @ResponseBody
    public String batchRestoreFiles(@RequestParam("fileIds") String fileIds) {
        try {
            String[] idArray = fileIds.split(",");
            boolean success = fileService.batchRestoreFromRecycle(idArray);
            return success ? successJson("recyclebin.batch.restore.success") : failJson("recyclebin.batch.restore.fail");
        } catch (Exception e) {
            return failJson("recyclebin.batch.restore.error", e.getMessage());
        }
    }

    /**
     * 批量永久删除文件
     */
    @PostMapping("/recycle/batchDelete")
    @ResponseBody
    public String batchPermanentlyDeleteFiles(@RequestParam("fileIds") String fileIds) {
        try {
            String[] idArray = fileIds.split(",");
            boolean success = fileService.batchPermanentlyDelete(idArray);
            return success ? successJson("recyclebin.batch.permanent.delete.success") : failJson("recyclebin.batch.permanent.delete.fail");
        } catch (Exception e) {
            return failJson("recyclebin.batch.permanent.delete.error", e.getMessage());
        }
    }

    @RequestMapping("/uploadFile")
    @ResponseBody
    public String uploadFile(MultipartHttpServletRequest request, @RequestParam("parentId") String parentId) throws IOException {
        MultipartFile multipartFile = request.getFile("fileName");
        String fileName = multipartFile.getOriginalFilename();

        fileIoService.uploadFile(parentId, fileName, multipartFile.getInputStream());

        return successJson("file.upload.success");
    }


    @RequestMapping("/copyFile")
    @ResponseBody
    public String copyFile(@RequestParam("parentId") String parentId, @RequestParam("srcUuidList") String srcUuidList) {
        fileIoService.copyFile(parentId, srcUuidList);
        return successJson("file.copy.success");
    }



    // 原有的previewFile方法被注释掉的部分可以保留或删除，这里选择保留
//    @GetMapping("/preview/{fileId}")
//    @ResponseBody
//    public ResponseEntity<InputStreamResource> previewFile(@PathVariable String fileId) throws IOException {
//        // 获取文件信息
//        PtFileEntity file = fileService.getFileById(fileId);
//        if (file == null) {
//            return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
//        }
//
//        // 验证文件类型是否为支持的媒体类型
//        String contentType = getContentType(file.getFileType());
//        if (contentType == null) {
//            return ResponseEntity.status(HttpStatus.UNSUPPORTED_MEDIA_TYPE)
//                    .body(null);
//        }
//
//        // 读取文件流
//        Path filePath = Paths.get(file.getFilePath());
//        InputStreamResource resource = new InputStreamResource(Files.newInputStream(filePath));
//
//        // 返回流式响应
//        return ResponseEntity.ok()
//                .contentType(MediaType.parseMediaType(contentType))
//                .contentLength(Files.size(filePath))
//                .header("Accept-Ranges", "bytes")
//                .header("Content-Disposition", "inline; filename=\"" + file.getFileName() + "\"")
//                .body(resource);
//    }
//
//    /**
//     * 确定文件的Content-Type
//     */
//    private String getContentType(String fileType) {
//        if (fileType.startsWith("video/")) {
//            return fileType;
//        } else if (fileType.startsWith("audio/")) {
//            return fileType;
//        } else if (fileType.contains("video") || fileType.contains("audio")) {
//            // 处理可能的类型映射
//            if (fileType.contains("mp4")) return "video/mp4";
//            if (fileType.contains("avi")) return "video/x-msvideo";
//            if (fileType.contains("mp3")) return "audio/mpeg";
//            if (fileType.contains("wav")) return "audio/wav";
//        }
//        return null;
//    }

    //创建文件夹
    @RequestMapping("/mkdirFileInfo")
    @ResponseBody
    public String mkdirFileInfo(@Param("parentId") String parentId, @Param("folderName") String folderName){

        fileIoService.mkdirFileInfo(parentId,folderName);
        return successJson("file.mkdir.success");
    }




    //文件查询q
    @RequestMapping("/queryFileInfoById")
    @ResponseBody
    public String queryFileInfoById(@RequestParam("fileUuid") String fileUuid){
        PtFileEntity ptFileEntity = fileService.queryFileInfoById(fileUuid);
        return JSON.toJSONString(ptFileEntity);
    }

    //文件修改q
    @RequestMapping("/modifyFileInfoById")
    @ResponseBody
    public String modifyFileInfoById(PtFileEntity entity){
        fileService.modifyFileInfoById(entity);
        return successJson("modify.file.success");
    }
    @RequestMapping("/getShareUrl")
    @ResponseBody
    public String getShareUrl(@Param("fileUuid") String fileUuid){
        String url = fileIoService.getShareUrl(fileUuid);
        return successJson("file.share.success",url);
    }

    @RequestMapping("/queryShareUrl")
    @ResponseBody
    public String queryShareUrl(@RequestParam("fileUuid") String fileUuid,@RequestParam("fileValidity") Integer fileValidity){
        String url = fileIoService.queryShareUrl(fileUuid,fileValidity);
        return successJson("file.share.success",url);
    }


    /**
     * 获取文件预览URL（复用分享链接逻辑）
     */
    @RequestMapping("/getPreviewUrl")
    @ResponseBody
    public String getPreviewUrl(@RequestParam("fileUuid") String fileUuid) {
        String url = fileIoService.getShareUrl(fileUuid);
        return successJson("file.preview.success", url);
    }

}
